import React, { Component } from 'react';
import Moment from 'moment';

import { Get, Post, PostString } from '../utils/fetch';
import Unit from '../utils/unit';

const index = 0;
const size = 10;

class Table extends Component {

    static defaultProps = {
        title: "",
        url: "",
        isGet: false,
        isPage: true,
        columns: [],
        params: {},
        paramsJson: true,
        dataList: null,
    };

    state = {
        page: {},
        pageIndex: index,
        pageSize: size,
        total: 0,
        dataList: this.props.dataList || []
    };

    componentDidMount = () => {
        let { url, params } = this.props;
        if (!url) {
            return;
        }
        this.load(url, params, this.state.pageIndex, this.state.pageSize);
    };

    componentWillReceiveProps = (props) => {
        // dataList changed
        if (props.dataList && this.state.dataList !== props.dataList) {
            this.setState({ dataList: props.dataList });
        }
        //url changed
        else if (props.url !== this.props.url) {
            this.setState({
                page: {},
                pageIndex: index,
                pageSize: size,
            });
            this.load(props.url, props.params, index, size);
        }
    };

    render = () => {
        return (
            <div className="row">
                <div className="col-lg-12">
                    <h2>
                        {this.props.title}
                        {this.props.subTitle}
                    </h2>
                    {this.props.children}
                    <div className="table-responsive">
                        <table className="table table-bordered table-hover">
                            <thead>
                                <tr>
                                    {this._renderHeader()}
                                </tr>
                            </thead>
                            <tbody>
                                {this._renderBody()}
                            </tbody>
                        </table>
                        {this._renderPage()}
                    </div>
                </div>
            </div>
        );
    };

    _renderPage = () => {
        let { isPage } = this.props;
        let { page, pageIndex } = this.state;
        pageIndex = pageIndex || 0;
        if (isPage) {
            let hasPre = pageIndex - 1 >= 0;
            let notNext = pageIndex + 1 >= page.totalPages;
            return (
                <nav>
                    <ul className="pager">
                        <li className={hasPre ? '' : 'disabled'}><a onClick={() => hasPre ? this.loadPage(--pageIndex) : ''}>上一页</a></li>
                        {'        '}
                        <li className={notNext ? 'disabled' : ''}><a onClick={() => notNext ? '' : this.loadPage(++pageIndex)}>下一页</a></li>
                    </ul>
                </nav>
            );
        }
    };

    _renderHeader = () => {
        return this.props.columns.map((column, index) => {
            return <th key={index}>{column.title}</th>;
        });
    };

    _renderBody = () => {
        return this.state.dataList.map((dataItem, itemIndex) => {
            let tds = [];
            this.props.columns.forEach((column, index) => {
                tds.push(<td key={index}>{column.render ? column.render(dataItem, itemIndex) : this._getItemValue(dataItem, column.name, column.type)}</td>);
            })
            return (<tr key={itemIndex}>{tds}</tr>);
        });
    };

    _getItemValue = (dataItem, prop, type) => {
        let r = dataItem,
            propName = "",
            props = prop.split('.');
        while (true) {
            propName = props.shift()
            if (r && propName) {
                r = r[propName];
            }
            else {
                break;
            }
        }
        if (r && type) {
            switch (type) {
                case 'date':
                    r = Moment(r).format('YYYY-MM-DD HH:mm:ss');
                    break;
                case 'tenThousand':
                    r = Unit.toTenThousand(r);
                    break;
                case 'yuan':
                    r = Unit.toYuan(r);
                    break;
                default:
            }
        }
        return r;
    };

    /**
     * 
     */
    load = (url, params, pageIndex, pageSize) => {
        let { isGet, isPage, paramsJson } = this.props;
        params = params || {};
        if (isPage) {
            if (url.indexOf('?') != -1){
                url += '&';
            }
            else {
                url += '?';
            }
            url += `page=${pageIndex}&size=${pageSize}`;
        }
        (isGet ? Get : paramsJson ? Post : PostString)(url, params)
            .then((r) => {
                this.setState({ dataList: r.content, total: r.totalElements, page: r });
            });
    };

    /**
     * 
     */
    loadPage = (pageIndex) => {
        this.setState({ pageIndex });
        this.load(this.props.url, this.props.params, pageIndex, this.state.pageSize);
    };

    /**
     * 
     */
    refresh = (params) => {
        this.load(this.props.url, params, this.state.pageIndex, this.state.pageSize);
    };
}

export default Table;